"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const tslib_1 = require("tslib");
const m_base_1 = tslib_1.__importDefault(require("../utils/m-base"));
const m_file_1 = tslib_1.__importDefault(require("../utils/m-file"));
const m_writer_1 = tslib_1.__importDefault(require("../services/m-writer"));
/**js+axios文件书写器 */
class WriterJsAxios extends m_writer_1.default {
    /**书写枚举 */
    async writeEnums() { }
    /**书写模型 */
    async writeModels() {
        const { data, dir } = this;
        for (const m of data.models) {
            const { name, description, uses, props } = m;
            const path = `${dir}/models/${name}.js`;
            //定义文件框架
            const lines = [];
            //添加文件提示
            lines.push(...this.getFileTips());
            //添加一个空行
            lines.push("\t");
            //添加模型备注
            lines.push(...m_base_1.default.toCNote(description));
            //添加模型定义开头
            lines.push(`export default class ${name} {`);
            //添加模型属性
            const body = [];
            for (const p of props)
                body.push(...this.getModelProp(p));
            lines.push(...m_base_1.default.ident(body, 2));
            //添加一个空行
            lines.push("\t");
            //添加模型构造器
            lines.push(...this.getModelConstructor(m));
            //添加模型结尾
            lines.push("}");
            //添加一个空行
            lines.push("\t");
            //写入文件
            await m_file_1.default.writeFile(path, m_base_1.default.toRows(lines));
        }
    }
    /**书写请求函数 */
    async writeMethods() {
        const { data, dir } = this;
        for (const m of data.methods) {
            const group = m.group || "";
            const base = m.base || "";
            const urls = m.urls || [];
            const funcs = m.funcs || [];
            const path = `${dir}/${group}.js`;
            //定义文件框架
            const lines = [];
            //添加文件提示
            lines.push(...this.getFileTips());
            //添加模型引用
            const imports = [];
            imports.push(`import axios from "axios";`);
            lines.push(...imports);
            //添加两个空行
            lines.push("\t\t");
            //添加请求项目名称
            const baseName = `const baseName = "${base}";`;
            lines.push(...[...m_base_1.default.toCNote("定义请求项目名称"), baseName]);
            //添加两个空行
            lines.push("\t\t");
            //添加请求地址
            const paths = [];
            for (const u of urls) {
                const { name, description, value } = u;
                const desc = m_base_1.default.toCNote(description);
                const dim = `export const ${name} = "${value}";`;
                paths.push(...[...desc, dim]);
            }
            lines.push(...paths);
            //添加两个空行
            lines.push("\t\t");
            //添加请求函数
            const apis = [];
            for (const f of funcs) {
                apis.push(...this.getMethodFunc(f));
            }
            lines.push(...apis);
            //添加一个空行
            lines.push("\t");
            //写入文件
            await m_file_1.default.writeFile(path, m_base_1.default.toRows(lines));
        }
    }
    /**获取请求函数定义 */
    getMethodFunc(func) {
        const { name, method, urlName, description } = func || {};
        const { inputParms, inputModel } = func || {};
        const hasModel = inputModel.length > 0;
        const parm = this.getMethodParm(inputParms);
        const parms = parm.filter((x) => !x.inPath).map((x) => x.name);
        const paths = parm.filter((x) => x.inPath).map((x) => x.name);
        //定义函数框架
        const lines = [];
        //添加函数注释
        lines.push(...m_base_1.default.toCNote(description));
        //添加函数定义
        let mParm = hasModel ? `reqBody, ` : "";
        if (parm.length > 0) {
            mParm = `${mParm}reqParm: { `;
            parm.forEach((x) => (mParm = `${mParm}${x.name}, `));
            mParm = `${m_base_1.default.trimStr(mParm, ",")} }, `;
        }
        mParm = `${mParm}reqConfig`;
        lines.push(`export function ${name}(${mParm}) {`);
        //添加函数任务
        let mConf = "";
        const task = [];
        task.push(`let reqUrl = ${urlName};`);
        task.push(`const reqConf = { ...reqConfig };`);
        task.push(`const reqHeaders = { baseName, ...reqConf.headers };`);
        if (parm.length > 0) {
            task.push(`const { ${parm.map((x) => x.name).join(", ")} } = reqParm;`);
        }
        if (paths.length > 0) {
            task.push(`const reqPaths = { ${paths.join(", ")} };`);
            task.push("reqUrl = reqUrl.replace(/\\{([^\\}]+)\\}/g, (m, p) => reqPaths[p]);");
        }
        if (parms.length > 0) {
            task.push(`const reqParams = { ...reqConf.params };`);
            task.push(`Object.assign(reqParams, { ${parms.join(", ")} });`);
            mConf = `{ ...reqConfig, ...{ headers: reqHeaders, params: reqParams } }`;
        }
        else {
            mConf = `{ ...reqConfig, ...{ headers: reqHeaders } }`;
        }
        task.push("return new Promise((resolve, reject) => {");
        //添加axios定义
        const axios = [];
        //请求实例处理
        let dim = "";
        if (method == "put" || method == "post") {
            const mData = hasModel ? "reqBody" : "null";
            dim = `const resTask = axios.${method}(reqUrl, ${mData}, ${mConf});`;
        }
        else {
            dim = `const resTask = axios.${method}(reqUrl, ${mConf});`;
        }
        axios.push(dim);
        //添加任务回调
        axios.push(`resTask.then(x => resolve(x.data));`);
        axios.push(`resTask.catch(x => reject(x));`);
        //把axios定义添加到任务定义中
        task.push(...m_base_1.default.ident(axios, 2));
        //任务结尾
        task.push("});");
        //把任务定义添加到文件框架中
        lines.push(...m_base_1.default.ident(task, 2));
        //添加函数结尾
        lines.push("}");
        return lines;
    }
    /**获取模型属性定义字符串 */
    getModelProp(prop) {
        const { name, description } = prop || {};
        const note = m_base_1.default.toCNote(description);
        const valueStr = this.getModelValueStr(prop);
        const dim = `${name} = ${valueStr};`;
        return [...note, dim];
    }
    /**获取模型构造函数定义字符串 */
    getModelConstructor(model) {
        const m = model || {};
        const props = m.props || [];
        const name = m.name || "";
        const desc = m.description || "";
        const lines = [];
        lines.push(...m_base_1.default.toCNote(desc || `实例化${name}`));
        lines.push(`constructor(data) {`);
        const body = [];
        body.push(`if (!data) return;`);
        for (const p of props) {
            const name = p.name || "";
            const value = this.getModelValueStr(p);
            body.push(`this.${name} = data.${name} || ${value};`);
        }
        lines.push(...m_base_1.default.ident(body, 2));
        lines.push(`}`);
        return m_base_1.default.ident(lines, 2);
    }
    /**获取请求函数参数 */
    getMethodParm(parm) {
        const dims = parm.map((x) => {
            const name = x.name || "";
            if (!name)
                return { name: "", inPath: false };
            return { name, inPath: x.inPath };
        });
        return dims.filter((x) => !!x.name);
    }
    /**获取默认值字符串 */
    getModelValueStr(prop) {
        const { type, required, nullable } = prop || {};
        const must = required || !nullable;
        const first = (type || [])[0] || {};
        const fType = first.type;
        const format = first.format || "";
        const num1 = "number,long,short,int,integer,int32,int64";
        const num2 = "double,float,decimal";
        const obj = "object,file,blob";
        const isDate = format.includes("date");
        if (fType == "array")
            return "[]";
        if (!must || isDate || obj.includes(fType))
            return "null";
        if (num1.includes(fType))
            return "0";
        if (num2.includes(fType))
            return "0.0";
        if (fType === "string")
            return `""`;
        if (fType === "boolean")
            return "false";
        return `new ${fType}()`;
    }
}
exports.default = WriterJsAxios;
/**注册js+axios书写器 */
m_writer_1.default.register("js+axios", WriterJsAxios);
